using System;

namespace Fadd.Logging
{
    /// <summary>
    /// The console logger is used to display logging in the console window.
    /// Different priorities are shown in different color, instead of showing the priority text.
    /// </summary>
    public class ConsoleLogger : Logger
    {
        private readonly ConsoleConfiguration _consoleConfiguration;

        /// <summary>
        /// Initializes a new instance of the <see cref="ConsoleLogger"/> class.
        /// </summary>
        /// <param name="logFormatter">The log formatter.</param>
        /// <param name="configuration">Configuration for the logger.</param>
        public ConsoleLogger(LogFormatter logFormatter, ILoggerConfiguration configuration)
            : base(logFormatter, configuration)
        {
			_consoleConfiguration = new ConsoleConfiguration();
        }


        #region ILogger Members

        /// <summary>
        /// Very detailed log messages, potentially of a high frequency and volume
        /// </summary>
        /// <param name="message">message written to the log.</param>
        public override void Trace(string message)
        {
            WriteMessage(_consoleConfiguration.TraceColor, message);
        }

        /// <summary>
        /// Very detailed log messages, potentially of a high frequency and volume
        /// </summary>
        /// <param name="message">message written to the log.</param>
        /// <param name="exception">an exception.</param>
        public override void Trace(string message, Exception exception)
        {
            WriteMessage(_consoleConfiguration.TraceColor, message, exception);
        }

        /// <summary>
        /// Less detailed and/or less frequent debugging messages
        /// </summary>
        /// <param name="message">message written to the log.</param>
        public override void Debug(string message)
        {
            WriteMessage(_consoleConfiguration.DebugColor, message);
        }

        /// <summary>
        /// Less detailed and/or less frequent debugging messages
        /// </summary>
        /// <param name="message">message written to the log.</param>
        /// <param name="exception">an exception.</param>
        public override void Debug(string message, Exception exception)
        {
            WriteMessage(_consoleConfiguration.DebugColor, message, exception);
        }

        /// <summary>
        /// Informational messages
        /// </summary>
        /// <param name="message">message written to the log.</param>
        public override void Info(string message)
        {
            WriteMessage(_consoleConfiguration.InfoColor, message);
        }

        /// <summary>
        /// Informational messages
        /// </summary>
        /// <param name="message">message written to the log.</param>
        /// <param name="exception">an exception.</param>
        public override void Info(string message, Exception exception)
        {
            WriteMessage(_consoleConfiguration.InfoColor, message, exception);
        }

        /// <summary>
        /// Warnings which don't appear to the user of the application
        /// </summary>
        /// <param name="message">message written to the log.</param>
        public override void Warning(string message)
        {
            WriteMessage(_consoleConfiguration.WarningColor, message);
        }

        /// <summary>
        /// Warnings which don't appear to the user of the application
        /// </summary>
        /// <param name="message">message written to the log.</param>
        /// <param name="exception">an exception.</param>
        public override void Warning(string message, Exception exception)
        {
            WriteMessage(_consoleConfiguration.WarningColor, message, exception);
        }

        /// <summary>
        /// Error messages
        /// </summary>
        /// <param name="message">message written to the log.</param>
        public override void Error(string message)
        {
            WriteMessage(_consoleConfiguration.ErrorColor, message);
        }

        /// <summary>
        /// Error messages
        /// </summary>
        /// <param name="message">message written to the log.</param>
        /// <param name="exception">an exception.</param>
        public override void Error(string message, Exception exception)
        {
            WriteMessage(_consoleConfiguration.ErrorColor, message, exception);
        }

        /// <summary>
        /// Fatal error messages. After a fatal error, the application usually terminates. 
        /// </summary>
        /// <param name="message">message written to the log.</param>
        public override void Fatal(string message)
        {
            WriteMessage(_consoleConfiguration.FatalColor, message);
        }

        /// <summary>
        /// Fatal error messages. After a fatal error, the application usually terminates. 
        /// </summary>
        /// <param name="message">message written to the log.</param>
        /// <param name="exception">an exception.</param>
        public override void Fatal(string message, Exception exception)
        {
            WriteMessage(_consoleConfiguration.FatalColor, message, exception);
        }

        #endregion


        private void WriteMessage(ConsoleColor color, string message)
        {
            lock (this)
            {
                Console.ForegroundColor = color;
                Console.WriteLine(FormatEntry(message, null));
                Console.ForegroundColor = _consoleConfiguration.DebugColor;
            }
        }

        private void WriteMessage(ConsoleColor color, string message, Exception exception)
        {
            lock (this)
            {
                Console.ForegroundColor = color;
                Console.WriteLine(FormatEntry(message, exception));
                Console.ForegroundColor = _consoleConfiguration.DebugColor;
            }
        }
    }
}